home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 7 / Apprentice-Release7.iso / Environments / Small Eiffel 0.4.8 / lib_std / bit_n.e < prev    next >
Text File  |  1997-04-13  |  7KB  |  295 lines

  1. -- Part of SmallEiffel -- Read DISCLAIMER file -- Copyright (C) 
  2. -- Dominique COLNET and Suzanne COLLIN -- colnet@loria.fr
  3. --
  4. expanded class BIT_N
  5. --
  6. -- Indexed Bit sequences of length `N'. This class is a template,
  7. -- not a real class; to obtain a meaningful class, replace `N' 
  8. -- with a positive integer throughout.
  9. -- 
  10. -- An INTEGER index can be used to access each bit of the sequence.
  11. -- The leftmost bit has index 1 and the rightmost bit has index `N'.
  12. --
  13. -- Note 1 : corresponding C mapping depends on actual `N' and is 
  14. --        PLATFORM dependant (see class PLATFORM).
  15. --        When `N' is in range [0  .. Character_bits], C type 
  16. --        is a simple "unsigned char".
  17. --        When `N' is in range [Character_bits+1 .. Integer_bits],
  18. --        C type is "unsigned".
  19. --        When `N' is greater than Integer_bits, C type is C array
  20. --        of "unsigned" of the form :
  21. --                 "unsigned storage[`N' div Integer_bits]"
  22. --        The array is obviously big enough to fit with `N'. As
  23. --        for previous mapping, the left most bit (at index 1 in 
  24. --        Eiffel) is always the left most in C memory.
  25. --
  26. -- Note 2 : Eiffel BIT code is portable. Generated C code for class
  27. --        BIT may not be portable (because sizeof(int) may change).
  28. --        To produce a portable C code, you can compile your Eiffel
  29. --        code using a machine with very small sizeof(int). Also note
  30. --        that doing this may run a little bit slowly.
  31. --
  32.  
  33. inherit 
  34.    BIT_N_REF 
  35.       redefine print_on, fill_tagged_out_memory
  36.    end;
  37.  
  38. feature {NONE}
  39.  
  40.    storage: POINTER;
  41.      -- The beginning of the storage zone (first byte
  42.      -- contains the beginning of the sequence).
  43.  
  44. feature -- Basic Accessing :
  45.    
  46.    count: INTEGER is
  47.      -- Number of bits in the sequence (the value of `N').
  48.       external "CSE"
  49.       end;
  50.  
  51.    item(idx: INTEGER): BOOLEAN is
  52.      -- True if i-th bit is 1, false otherwise.
  53.       require
  54.      inside_bounds: 1 <= idx and then idx <= count
  55.       external "CSE"
  56.       end;
  57.    
  58.    put(value: BOOLEAN; idx: INTEGER) is
  59.      -- Set bit `idx' to 1 if value is true, 0 otherwise.
  60.       require
  61.      inside_bounds: 1 <= idx and idx <= count
  62.       external "CSE"
  63.       ensure
  64.      value = item(idx)
  65.       end;
  66.  
  67.    put_1(idx: INTEGER) is
  68.      -- Set bit `idx' to 1.
  69.       require
  70.      inside_bounds: 1 <= idx and idx <= count
  71.       external "CSE"
  72.       ensure
  73.      item(idx)
  74.       end;
  75.  
  76.    put_0(idx: INTEGER) is
  77.      -- Set bit `idx' to 0.
  78.       require
  79.      inside_bounds: 1 <= idx and idx <= count
  80.       external "CSE"
  81.       ensure
  82.      not item(idx)
  83.       end;
  84.  
  85. feature -- Rotating and shifting :
  86.  
  87.    infix "^" (s: INTEGER): like Current is 
  88.      -- Sequence shifted by `s' positions (positive `s' shifts 
  89.          -- right, negative left; bits falling off the sequence's
  90.          -- bounds are lost).
  91.      -- See also infix "@>>" and infix "@<<".
  92.       require
  93.      s.abs<count;
  94.       do
  95.      if s >= 0 then
  96.         Result := Current @>> s;
  97.      else
  98.         Result := Current @<< -s;
  99.      end;
  100.       end;
  101.  
  102.    infix "@>>" (s: INTEGER): like Current is 
  103.      -- Sequence shifted right by `s' positions.
  104.      -- Same as infix "^" when `s' is positive (may run a little 
  105.      -- bit faster).
  106.       require
  107.          s > 0
  108.       external "CSE"
  109.       end;
  110.  
  111.    infix "@<<" (s: INTEGER): like Current is 
  112.      -- Sequence shifted left by `s' positions.
  113.      -- Same as infix "^" when `s' is negative (may run a little 
  114.          -- bit faster.
  115.       require
  116.          s > 0
  117.       external "CSE"
  118.       end;
  119.  
  120.    infix "#" (s: INTEGER): like Current is 
  121.      -- Sequence rotated by `s' positions (positive right,
  122.      -- negative left).
  123.       require
  124.      s.abs<count;
  125.       do
  126.      if s >= 0 then
  127.         Result := Current #>> s;
  128.      else
  129.         Result := Current #>> -s;
  130.      end;
  131.       end
  132.  
  133.    infix "#>>" (s: INTEGER): like Current is 
  134.      -- Sequence rotated by `s' positions right.      
  135.       require
  136.      s >= 0;
  137.      s < count
  138.       local
  139.      i: INTEGER;
  140.      bit: BOOLEAN;
  141.       do
  142.      from
  143.         i := s;
  144.         Result := Current;
  145.      until
  146.         i = 0
  147.      loop
  148.         bit := Result.item(count);
  149.         Result := Result @>> 1;
  150.         Result.put(bit,1);
  151.         i := i - 1;
  152.      end;
  153.       end;
  154.    
  155.    infix "#<<" (s: INTEGER): like Current is 
  156.            -- Sequence rotated by `s' positions left.      
  157.       require
  158.      s >= 0;
  159.      s < count
  160.       local
  161.      i: INTEGER;
  162.      bit: BOOLEAN;
  163.       do
  164.      from
  165.         i := s;
  166.         Result := Current;
  167.      until
  168.         i = 0
  169.      loop
  170.         bit := Result.item(1);
  171.         Result := Result @<< 1;
  172.         Result.put(bit,count);
  173.         i := i - 1;
  174.      end;
  175.       end;
  176.    
  177. feature -- Bitwise Logical Operators :
  178.  
  179.    infix "and" (other: like Current): like Current is
  180.      -- Bitwise `and' of Current with `other'
  181.       external "CSE"
  182.       end;
  183.  
  184.    infix "implies" (other: like Current): like Current is
  185.      -- Bitwise implication of Current with `other'
  186.       do
  187.          Result := not (Current or other);
  188.       end;
  189.  
  190.    prefix "not": like Current is
  191.      -- Bitwise `not' of Current.
  192.       external "CSE"
  193.       end;
  194.  
  195.    infix "or" (other: like Current): like Current is
  196.      -- Bitwise `or' of Current with `other'
  197.       external "CSE"
  198.       end;
  199.  
  200.    infix "xor" (other : like Current) : like Current is
  201.      -- Bitwise `xor' of Current with `other'
  202.       external "CSE"
  203.       end;
  204.  
  205. feature -- Conversions :
  206.  
  207.    to_string: STRING is
  208.      -- String representation of bit sequence. 
  209.          -- A zero bit is mapped to '0', a one bit to '1'. 
  210.          -- Leftmost bit is at index 1 in the returned string.
  211.      --
  212.      -- Note: see `append_in' to save memory.
  213.       do
  214.      tmp_string.clear;
  215.      append_in(tmp_string);
  216.      Result := tmp_string.twin;
  217.       ensure then
  218.      Result.count = count
  219.       end;
  220.    
  221.    to_integer: INTEGER is
  222.       require
  223.          count <= Integer_bits
  224.       do
  225.          c_inline_c("R=C;");
  226.       end;
  227.  
  228.    to_character: CHARACTER is
  229.       require
  230.          count <= Character_bits
  231.       do
  232.          c_inline_c("R=C;");
  233.       end;
  234.  
  235. feature -- Others :
  236.  
  237.    all_cleared: BOOLEAN is
  238.          -- Are all bits set to 0 ?
  239.       local
  240.          i: INTEGER;
  241.       do
  242.          from
  243.             Result := true;
  244.             i := count;
  245.          until
  246.             not Result or else i = 0
  247.          loop
  248.             Result := not item(i);
  249.             i := i - 1;
  250.          end;
  251.       end;
  252.  
  253. feature -- Printing :
  254.  
  255.    append_in(str: STRING) is
  256.       local
  257.      i: INTEGER;
  258.       do
  259.      from  
  260.         i := 1;
  261.      until
  262.         i > count
  263.      loop
  264.         if item(i) then
  265.            str.extend('1');
  266.         else
  267.            str.extend('0');
  268.         end;
  269.         i := i + 1;
  270.      end;
  271.       end;
  272.    
  273.    print_on(file: STD_FILE_WRITE) is
  274.       do
  275.      tagged_out_memory.clear;
  276.      Current.append_in(tagged_out_memory);
  277.      tagged_out_memory.extend('B');
  278.      file.put_string(tagged_out_memory);
  279.       end;
  280.  
  281.    fill_tagged_out_memory is
  282.       do
  283.      Current.append_in(tagged_out_memory);
  284.      tagged_out_memory.extend('B');
  285.       end;
  286.  
  287. feature {NONE}
  288.  
  289.    tmp_string: STRING is
  290.       once
  291.          !!Result.make(128);
  292.       end;
  293.  
  294. end -- BIT_N
  295.